2.4 - Your First Hello, World Bot
In programming, a "Hello, World!" application is the simplest possible program that proves a new system is working. Our goal here is the same: we will build a bot that does nothing in-game but prints messages to your console.
This exercise will teach you the fundamental structure and lifecycle of every bot you will build from now on.
Chapter Checklist
- Task 1: Create the Python file for the
HelloBot
. - Task 2: Understand the bot's lifecycle diagram.
- Task 3: Run the bot and observe the output.
- Task 4: Verify that the bot completes its full lifecycle.
The Bot's Lifecycle
Every python-sc2
bot follows a simple, predictable lifecycle. Understanding this flow is the key to knowing where to place your code.
(Game Starts)
|
v
[ on_start() ] <-- Runs ONCE at the beginning for setup.
|
|--------------------------.
| |
v | (Loop)
[ on_step() ] <-- Runs REPEATEDLY, many times per second.
| |
'--------------------------'
|
v
[ on_end() ] <-- Runs ONCE after the game has finished.
|
v
(Game Ends)
Step 1: The Code
Create a new file named hello_bot.py
and paste the following code into it.
# hello_bot.py
# =================================================================
# IMPORTS: We are importing necessary components from the sc2 library
# =================================================================
from sc2.main import run_game # The function that starts the game
from sc2 import maps # The function for loading maps
from sc2.bot_ai import BotAI # The base class for our bot
from sc2.player import Bot, Computer # Defines the players in the game
from sc2.data import Difficulty, Race # Defines race and game difficulty
class HelloBot(BotAI):
"""A bot to demonstrate the fundamental lifecycle."""
async def on_start(self):
"""Runs once, at the start of the game."""
print("Lifecycle: on_start() - Game has begun!")
async def on_step(self, iteration: int):
"""Runs on every game step (frame)."""
if iteration % 200 == 0:
# Print a message every 200 steps to show this is looping.
print(f"Lifecycle: on_step() - Iteration: {iteration}")
async def on_end(self, game_result: Result):
"""Runs once, after the game is over."""
print("Lifecycle: on_end() - Game has finished!")
print(f"The game result was: {game_result}")
if __name__ == "__main__":
main.run_game(
maps.get("AbyssalReefLE"),
[
Bot(Race.Terran, HelloBot()),
Computer(Race.Zerg, Difficulty.Hard), # Add an AI to ensure the game ends.
],
realtime=False, # Run as fast as possible.
save_replay_as="HelloBotReplay.SC2Replay",
)
Step 2: Anatomy of the Bot
This code has two main parts: the bot's "brain" (the HelloBot
class) and the "launcher" (main.run_game
). Let's dissect the brain.
Component | Code | Role |
---|---|---|
The Bot Class | class HelloBot(BotAI): | This is the blueprint for your bot. It inherits all the core capabilities from the library's BotAI class. |
The Setup Method | async def on_start(self): | This is your bot's constructor. It's the perfect place for setup logic that only needs to run once. |
The Main Loop | async def on_step(self, ...): | This is the heart of the bot. Almost all your decision-making logic (to build, fight, or expand) will live here. |
The Cleanup Method | async def on_end(self, ...): | This is your bot's destructor. It's ideal for post-game analysis or saving learned data. The game_result tells you if you won or lost. |
Step 3: Execution and Verification
- Activate your virtual environment.
(venv)
- Run the script from your terminal.
python hello_bot.py
Expected Outcome:
Because we set realtime=False
and added an opponent, the game will run very quickly and you won't see much on screen. The important part is the output in your terminal. You will see messages appear in a specific order, proving the lifecycle works as expected.
Lifecycle: on_start() - Game has begun!
Lifecycle: on_step() - Iteration: 0
Lifecycle: on_step() - Iteration: 200
Lifecycle: on_step() - Iteration: 400
...
Lifecycle: on_end() - Game has finished!
The game result was: Result.Victory
Congratulations. You have successfully created a bot and verified its core execution lifecycle. You are now ready to add actions inside this structure.